package com.beiding.jsonanalyzer.analyze.func.base;

import com.beiding.jsonanalyzer.Key;
import com.beiding.jsonanalyzer.analyze.KeyMode;
import com.beiding.jsonanalyzer.analyze.KeyUtils;
import com.beiding.jsonanalyzer.analyze.ValueUtils;
import com.beiding.jsonanalyzer.analyze.func.FuncBase;
import com.beiding.jsonanalyzer.analyze.func.FuncFactory;
import com.beiding.jsonanalyzer.flow.ValueNode;

import java.util.Collections;
import java.util.List;

/**
 * 用于从批中获取最后一个取值
 * 通常这是最后一级
 *
 * 比较特殊
 *
 */
public class LastGet extends FuncFactoryAdaptor<LastGet.F> {

    /**
     * 给定key以获取
     *
     * @param key
     * @return
     */
    public static LastGet of(Object key) {

        LastGet lastGet = new LastGet();


        if (!(key instanceof FuncFactory)) {
            key = ValueGet.of(key);
        }

        Object z = key;

        lastGet.addForFunc(f -> {
            f.valueGet = ((FuncFactory) z).createInstance();
        });


        return lastGet;
    }

    /**
     * 返回自身
     *
     * @return
     */
    public static LastGet of() {

        return of(Key.parse(""));
    }

    @Override
    protected F newInstance() {
        return new F();
    }

    /**
     * 内核函数
     */
    static class F implements FuncBase {

        private FuncBase valueGet;

        /**
         * 最后一个值对象
         */
        private ValueNode last;


        @Override
        public boolean checkAgg() {

            //本身是不主动聚合的
            return false;
        }


        @Override
        public Object executeOne(ValueNode valueNode) {

            //单个值获取的话,直接返回结果
            return valueGet.executeOne(valueNode);
        }

        /**
         * 放入聚合的话,只记录最后一个值
         *
         * @param valueNode
         */
        @Override
        public void pugAgg(ValueNode valueNode) {
            last = valueNode;
        }

        /**
         * 重置时清空最后一个值
         */
        @Override
        public void resetAgg() {
            last = null;
        }

        /**
         * 获取最终聚合的结果
         *
         * @return
         */
        @Override
        public Object aggGet() {
            if (last == null) {
                return null;
            }
            //无论内核函数是否支持聚合,最后都取其非聚合的值
            return valueGet.executeOne(last);
        }

        @Override
        public String toString() {
            return valueGet.toString();
        }
    }

    /**
     * 取值函数工厂
     * 只简单取值
     */
    private static class ValueGet extends FuncFactoryAdaptor<ValueGet.F> {


        public static ValueGet of(Object k) {
            ValueGet valueGet = new ValueGet();
            valueGet.addForFunc(f -> {
                f.k = KeyUtils.handleKey(k, KeyMode.TEXT_TO_KEY);
            });
            return valueGet;
        }

        @Override
        protected F newInstance() {
            return new F();
        }


        static class F implements FuncBase {

            private Object k;

            @Override
            public boolean checkAgg() {
                return false;
            }

            @Override
            public Object executeOne(ValueNode valueNode) {
                return ValueUtils.execExpression(valueNode.get(), k, Object.class);
            }

            @Override
            public void pugAgg(ValueNode valueNode) {

            }

            @Override
            public void resetAgg() {
            }

            @Override
            public List<Object> aggGet() {
                return Collections.emptyList();
            }

            @Override
            public String toString() {
                if (k instanceof String) {
                    return "'" + k + "'";
                }
                return k+"";
            }
        }


    }

}
